package com.zt.reggie.controller;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.zt.reggie.common.R;
import com.zt.reggie.dto.DishDto;
import com.zt.reggie.dto.SetMealDto;
import com.zt.reggie.entity.Category;
import com.zt.reggie.entity.Dish;
import com.zt.reggie.entity.SetMeal;
import com.zt.reggie.entity.SetMealDish;
import com.zt.reggie.service.CategoryService;
import com.zt.reggie.service.DishService;
import com.zt.reggie.service.SetMealDishService;
import com.zt.reggie.service.SetMealService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.web.bind.annotation.*;

import java.util.List;
import java.util.stream.Collectors;

/**
 * @author 挚爱之夕
 * @version 1.0
 * @implSpec com.zt.reggie.controller
 * @since 2023 - 02 - 27 - 14:35
 */
@RestController
@Slf4j
@RequestMapping("/setmeal")
public class SetMealController {
    @Autowired
    private SetMealDishService setMealDishService;
    @Autowired
    private SetMealService setMealService;
    @Autowired
    private CategoryService categoryService;

    @Autowired
    private DishService dishService;

    /**
     * 新增套餐并添加套餐和菜品的关系
     * @param setMealDto
     * @return
     */
    @PostMapping
    @CacheEvict(value = "setMealCache", allEntries = true)
    public R<String> save(@RequestBody SetMealDto setMealDto){
        log.info("SetMealDto:{}", setMealDto.toString());

        setMealService.saveWithDish(setMealDto);
        return R.success("保存套餐成功!");
    }

    /**
     * 分页查询套餐信息
     * @param page
     * @param pageSize
     * @param name
     * @return
     */
    @GetMapping("/page")
    public R<Page<SetMealDto>> page(Integer page, Integer pageSize, String name){
        //条件构造器
        LambdaQueryWrapper<SetMeal> wrapper = new LambdaQueryWrapper<>();
        wrapper.like(name != null, SetMeal::getName, name);
        wrapper.orderByDesc(SetMeal::getUpdateTime);
        Page<SetMeal> pageInfo = new Page<>(page, pageSize);

        setMealService.page(pageInfo, wrapper);
        //Page<SetMeal> -> Page<SetMealDto>
        Page<SetMealDto> setMealDtoPage = new Page<>();
        BeanUtils.copyProperties(pageInfo, setMealDtoPage, "records");

        //需要分类名称
        List<SetMealDto> list = pageInfo.getRecords().stream().map(e -> {
            SetMealDto setMealDto = new SetMealDto();
            BeanUtils.copyProperties(e, setMealDto);
            Category category = categoryService.getById(e.getCategoryId());
            if(category != null)
                setMealDto.setCategoryName(category.getName());
            return setMealDto;
        }).collect(Collectors.toList());

        setMealDtoPage.setRecords(list);
        return R.success(setMealDtoPage);
    }

    /**
     * 删除套餐
     * @param ids
     * @return
     */
    @DeleteMapping
    @CacheEvict(value = "setMealCache", allEntries = true)
    public R<String> delete(@RequestParam List<Long> ids){
        log.info("deleteMeal:ids={}", ids.toString());
        setMealService.deleteWithDish(ids);
        return R.success("删除套餐成功!");
    }

    /**
     * 查询套餐明细 和 关联的菜品
     * @param id
     * @return
     */
    @GetMapping("/{id}")
    public R<SetMealDto> get(@PathVariable Long id){
        SetMealDto setMealDto = setMealService.getByIdWithDish(id);
        return R.success(setMealDto);
    }

    /**
     * 修改套餐 和 关联的菜品
     * @param setMealDto
     * @return
     */
    @PutMapping
    public R<String> update(@RequestBody SetMealDto setMealDto){
        setMealService.updateWithDish(setMealDto);
        return R.success("修改套餐成功!");
    }

    /**
     * 修改套餐状态
     * @param status
     * @param ids
     * @return
     */
    @PostMapping("/status/{status}")
    public R<String> change(@PathVariable Integer status, @RequestParam List<Long> ids){
        setMealService.changeStatus(ids, status);
        return R.success("操作成功!");
    }

    /**
     * 根据categoryId 和 status 查询
     * @param setMeal
     * @return
     */
    @GetMapping("/list")
    @Cacheable(value = "setMealCache", key = "#setMeal.categoryId + '_' + #setMeal.status")
    public R<List<SetMeal>> list(SetMeal setMeal){
        LambdaQueryWrapper<SetMeal> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(setMeal.getStatus() != null, SetMeal::getStatus, setMeal.getStatus());
        wrapper.eq(setMeal.getCategoryId() != null, SetMeal::getCategoryId, setMeal.getCategoryId());

        List<SetMeal> list = setMealService.list(wrapper);

        return R.success(list);
    }

    /**
     * 查询套餐详情
     * @param setMealId
     * @return
     */
    @GetMapping("/dish/{setMealId}")
    public R<List<DishDto>> getDishes(@PathVariable Long setMealId){
        LambdaQueryWrapper<SetMealDish> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(SetMealDish::getSetmealId, setMealId);

        List<SetMealDish> list = setMealDishService.list(wrapper);

        List<DishDto> dishDtoList = list.stream().map(e -> {
            DishDto dishDto = new DishDto();
            //份数
            dishDto.setCopies(e.getCopies());
            //查菜品基本信息
            Dish dish = dishService.getById(e.getDishId());
            BeanUtils.copyProperties(dish, dishDto);
            return dishDto;
        }).collect(Collectors.toList());
        return R.success(dishDtoList);
    }
}
